#include <iostream>
#include <vector>
#include <unistd.h>
#include "Thread.hpp"
#include "RingQueue.hpp"

using namespace std;
using namespace ThreadModule;

using ringqueue_t=RingQueue<int>;

void Productor(ringqueue_t& rq,string threadname)
{
    int data=10;
    while(true)  
    {
      rq.EnQueue(data);
      cout<<"productor product data:"<<data<<"["<<threadname<<"]"<<endl;
      data++;
      sleep(1);
    }
}

void Consumer(ringqueue_t& rq,string threadname)
{
    while(true)
    {
        int data;
        rq.DeQueue(&data);
        cout<<"consumer get data:"<<data<<"["<<threadname<<"]"<<endl;
    }
}

void InitCommon(vector<Thread<ringqueue_t>>* threads,int threadnum,ringqueue_t& rq,func_t<ringqueue_t> func,string who)
{
    for(int i=0;i<threadnum;i++)
    {
        string threadname="thread -"+to_string(i+1)+" -"+who;
        Thread<ringqueue_t> t(func,rq,threadname);
        threads->push_back(t);
    }
}

void InitProductor(vector<Thread<ringqueue_t>>* threads,int threadnum,ringqueue_t& rq)
{
    InitCommon(threads,threadnum,rq,Productor,"productor");
}

void InitConsumer(vector<Thread<ringqueue_t>>* threads,int threadnum,ringqueue_t& rq)
{
    InitCommon(threads,threadnum,rq,Consumer,"consumer");
}

void StartAll(vector<Thread<ringqueue_t>>& threads)
{
    for(auto& thread:threads)
    {
        thread.Start();
    }
}

void WaitAllThread(vector<Thread<ringqueue_t>>& threads)
{
    for(auto& thread:threads)
    {
        thread.Join();
    }
}

int main()
{
   ringqueue_t* rq=new ringqueue_t(10);
    vector<Thread<ringqueue_t>> threads;

    InitProductor(&threads,3,*rq);
    InitConsumer(&threads,2,*rq);

    //启动线程
    StartAll(threads);
    WaitAllThread(threads);
    return 0;
}